home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
System Booster
/
System Booster.iso
/
Archives
/
Drivers
/
vc_2_2.lha
/
ParNet
/
Source
/
task.c
< prev
next >
Wrap
C/C++ Source or Header
|
1994-11-01
|
3KB
|
141 lines
/*
** $Header: SRC:CVSROOT/Vector/ParNet/task.c,v 1.1.1.1 1994/06/23 02:39:41 Barnard Exp $
*/
/*
** This code was originally written by Matthew Dillon and put into Public Domain
**
** All changes concerning the adaption of Matt's original code to the
** Vector Connection I/O board are © 1991-1994 by Henning Schmiedehausen
** All rights for this changes are reserved. The original code is Public Domain
**
** This code is distributed with the expressed written permission of Matthew
** Dillon (Thank you very much, Matt)
**
*/
/*
* TASK.C
*
* -Accept packets to send to network
* -Receive data from network
*
* ParWrite(destaddr, buf, bytes)
*/
#include "defs.h"
#include "parnet_asm.h"
#include "task_protos.h"
#include "parnet_protos.h"
#include <proto/exec.h>
typedef struct {
uword Port; /* destination port */
uword ChkSum; /* data checksum */
ulong Bytes; /* # of bytes */
} Header;
char DataBuf[MAXPKTSIZE];
Header Hdr;
long TLock[2] = { 0, 0 };
static short Cnt = 0;
void
CParNetTask()
{
long mask;
Unit *unit;
Packet *packet;
long n;
for (;;) {
SetPIOInt();
mask = Wait(SIGBREAKF_CTRL_E|SIGBREAKF_CTRL_F);
LockAddr(TLock);
if (mask & SIGBREAKF_CTRL_F) { /* packet pending */
data:
if (ParDataReady() > 0) {
n = ParReadV(&Hdr, sizeof(Hdr), DataBuf, MAXPKTSIZE, NULL, NULL);
/*sprintf(StickyPort->DebugBuf, "%03d READ %6ld", Cnt++, n);*/
if (n >= sizeof(Hdr) && n >= sizeof(Hdr) + Hdr.Bytes) {
if (unit = FindUnitForPort(Hdr.Port)) {
packet = AllocParPacket(NULL, unit, DataBuf, Hdr.Bytes, NULL, 0);
LockAddr(unit->UnitLock);
(*packet->io_Unit->DataFunc)('r', packet, n - sizeof(Hdr));
UnlockAddr(unit->UnitLock);
}
}
}
}
if (mask & SIGBREAKF_CTRL_E) { /* port */
while (packet = (Packet *)GetMsg(&DevBase->Port)) {
n = OutputPacket(packet);
if (n == -2) {
Forbid();
AddHead(&DevBase->Port.mp_MsgList, (struct Node *)packet);
Permit();
goto data;
}
}
}
UnlockAddr(TLock);
}
}
OutputPacket(packet)
Packet *packet;
{
long n;
Unit *unit = packet->io_Unit;
Hdr.Port = packet->DestPort;
Hdr.ChkSum= 0;
Hdr.Bytes = packet->DLen1 + packet->DLen2;
n = ParWriteV(packet->DestAddr, &Hdr, sizeof(Hdr), packet->Data1, packet->DLen1, packet->Data2, packet->DLen2, NULL, NULL);
/* sprintf(StickyPort->DebugBuf, "%03d WRITE %6ld", Cnt++, n); */
if (n == -2) /* can't write, pending rcv */
return(n);
LockAddr(unit->UnitLock);
if (n == sizeof(Hdr) + packet->DLen1 + packet->DLen2)
(*unit->DataFunc)('w', packet, n - sizeof(Hdr));
else
(*unit->DataFunc)('W', packet, n - sizeof(Hdr));
UnlockAddr(unit->UnitLock);
return(n);
}
/*
* Queue packet for write. If QUICKIO is requested and the packet can be
* sent manually it is, else it is queued to the task.
*/
void
QueuePacketForWrite(packet)
Packet *packet;
{
Iob *iob = packet->iob;
if ((iob->io_Flags & IOF_QUICK) && TryLockAddr(TLock) > 0) {
if (OutputPacket(packet) != -2) {
UnlockAddr(TLock);
return;
}
/*
* Can't write packet, rcv packet pending.
*/
UnlockAddr(TLock);
}
iob->io_Flags &= ~IOF_QUICK;
iob->io_Flags |= IOF_QUEUED;
PutMsg(&DevBase->Port, &packet->Msg);
}